﻿namespace com.crownpack
{
    using System.Collections.Generic;

    using com.crownpack.Extensions.SharePointExtensions;
    using com.crownpack.Extensions.StringExtensions;

    using Microsoft.BusinessData.MetadataModel;
    using Microsoft.BusinessData.Runtime;
    using Microsoft.SharePoint;
    using Microsoft.SharePoint.Administration;
    using Microsoft.SharePoint.BusinessData.SharedService;

    using ReferenceObject = Customer;

    /// <summary>
    /// References the following:
    /// ...\14\ISAPI\Microsoft.BusinessData.dll
    /// </summary>
    public class CustomerDao
    {
        #region Constructors

        public CustomerDao( string currentWebUrl )
        {
            CurrentWebUrl = currentWebUrl;
        }

        public CustomerDao( )
        {
            CurrentWebUrl = SPContext.Current.Web.Url;
        }

        #endregion Constructors

        #region Properties

        string CurrentWebUrl
        {
            get;
            set;
        }

        #endregion Properties

        #region Methods

        public ReferenceObject GetByLocationNo( int parentCustomerNo, int locationNo, string sourceList )
        {
            using ( SPSite spSite = new SPSite( CurrentWebUrl ) )
            {
                using ( SPWeb spWeb = spSite.OpenWeb( ) )
                {
                    using ( new SPServiceContextScope( SPServiceContext.GetContext( spSite ) ) )
                    {
                        BdcService service = SPFarm.Local.Services.GetValue<BdcService>( );
                        IMetadataCatalog catalog = service.GetDatabaseBackedMetadataCatalog( SPServiceContext.Current );

                        //IEntity entity = catalog.TryGetEntity( spSite.Url, sourceList );
                        IEntity entity = catalog.GetEntity( spSite.Url, sourceList );

                        if ( entity != null )
                        {
                            ILobSystemInstance LobSysteminstance = entity.GetLobSystem( ).GetLobSystemInstances( )[ 0 ].Value;
                            IMethodInstance method = entity.GetMethodInstance( "Read List", MethodInstanceType.Finder );
                            IEntityInstanceEnumerator handle = entity.FindFiltered( method.GetFilters( ), LobSysteminstance );

                            ReferenceObject o = null;

                            while ( handle.MoveNext( ) )
                            {
                                if ( handle.Current[ Layout.ParentCustomerNo ].ToString( ).Equals( parentCustomerNo.ToString( ) ) )
                                {
                                    if ( handle.Current[ Layout.LocationNo ].ToString( ).Equals( locationNo.ToString( ) ) )
                                    {
                                        Dictionary<string, string> d = new Dictionary<string, string>( );
                                        foreach ( string key in Layout.Keys )
                                        {
                                            try
                                            {
                                                string value = handle.Current[ key ].ToString( );
                                                d.Add( key, value );
                                            }
                                            catch
                                            {
                                                IgnoreError( );
                                            }
                                        }
                                        if ( d.Count > 0 )
                                            o = new ReferenceObject( d );
                                        break;
                                    }
                                }
                            }
                            return o;
                        }
                        else
                            return null;
                    }
                }
            }
        }

        public List<ReferenceObject> GetByParentCustomerNo( int parentCustomerNo, string sourceList )
        {
            List<ReferenceObject> l = new List<ReferenceObject>( );

            SPSecurity.RunWithElevatedPrivileges( delegate( )
            {
                using ( SPSite spSite = new SPSite( CurrentWebUrl ) )
                {
                    using ( SPWeb spWeb = spSite.OpenWeb( ) )
                    {
                        using ( new SPServiceContextScope( SPServiceContext.GetContext( spSite ) ) )
                        {
                            BdcService service = SPFarm.Local.Services.GetValue<BdcService>( );
                            IMetadataCatalog catalog = service.GetDatabaseBackedMetadataCatalog( SPServiceContext.Current );

                            //IEntity entity = catalog.TryGetEntity( spSite.Url, sourceList );
                            IEntity entity = catalog.GetEntity( spSite.Url, sourceList );

                            if ( entity != null )
                            {
                                ILobSystemInstance LobSysteminstance = entity.GetLobSystem( ).GetLobSystemInstances( )[ 0 ].Value;
                                IMethodInstance method = entity.GetMethodInstance( "Read List", MethodInstanceType.Finder );
                                IEntityInstanceEnumerator handle = entity.FindFiltered( method.GetFilters( ), LobSysteminstance );

                                while ( handle.MoveNext( ) )
                                {
                                    if ( handle.Current[ Layout.ParentCustomerNo ].ToString( ).Equals( parentCustomerNo.ToString( ) ) )
                                    {
                                        Dictionary<string, string> d = new Dictionary<string, string>( );
                                        foreach ( string key in Layout.Keys )
                                        {
                                            try
                                            {
                                                string value = handle.Current[ key ].ToString( );
                                                d.Add( key, value );
                                            }
                                            catch
                                            {
                                                IgnoreError( );
                                            }
                                        }
                                        if ( d.Count > 0 )
                                            l.Add( new ReferenceObject( d ) );
                                    }
                                }
                                l.Sort( ( a, b ) => a.LocationName.TryTrim( ).CompareTo( b.LocationName.TryTrim( ) ) );
                            }
                        }
                    }
                }
            } );
            return l;
        }

        public string GetEntityName( string sourceList )
        {
            using ( SPSite spSite = new SPSite( CurrentWebUrl ) )
            {
                using ( SPWeb spWeb = spSite.OpenWeb( ) )
                {
                    using ( new SPServiceContextScope( SPServiceContext.GetContext( spSite ) ) )
                    {
                        BdcService service = SPFarm.Local.Services.GetValue<BdcService>( );
                        IMetadataCatalog catalog = service.GetDatabaseBackedMetadataCatalog( SPServiceContext.Current );

                        IEntity entity = catalog.TryGetEntity( spSite.Url, sourceList );
                        //IEntity entity = catalog.GetEntity( spSite.Url, sourceList );
                        return entity != null ? entity.Name : string.Empty;
                    }
                }
            }
        }

        void IgnoreError( )
        {
            const string Notice = "This documents that the error condition is ignored.";
        }

        #endregion Methods
    }
}